import re
from playwright.sync_api import sync_playwright
import requests
import time
PAT = re.compile(r"\.m3u8($|\?|#)", re.I)
URL = "https://www.yinhuadm.xyz/p/4870-1-2.html"
from concurrent.futures import ThreadPoolExecutor, as_completed

def ll(ts_url, save_path):
    try:
        with requests.get(ts_url, stream=True, timeout=10) as r:
            r.raise_for_status()
            with open(save_path, 'wb') as ff:
                for chunk in r.iter_content(chunk_size=8192):
                    if chunk:
                        ff.write(chunk)
        return f"[OK] {save_path}"
    except Exception as e:
        return f"[ERR] {save_path} -> {e}"


def m3u8(url = URL):
    with sync_playwright() as pw:
        browser = pw.chromium.launch(headless=False)
        ctx = browser.new_context()
        page = ctx.new_page()

        try:
            # 先挂监听，再触发动作；满足条件立即返回
            with page.expect_event(
                "request",
                predicate=lambda r: PAT.search(r.url) is not None,
                timeout=30000,  # 可按需调大
            ) as req_info:
                page.goto(URL, wait_until="domcontentloaded")

            req = req_info.value
            print("[m3u8]", req.method, req.url)

            u = str(req.url)

            r = str(requests.get(u).content).split('\\n')[-1].replace("'","")
            print(r)

            u = u.replace('index.m3u8',r)
            print(u)

            rt = requests.get(u).content.decode('utf-8').split('\n')
            print(type(rt),rt)

            tasks=[]

            for i in rt:
                if '.ts' in i:
                    tasks.append(u.replace('mixed.m3u8',i))



            with ThreadPoolExecutor(max_workers=100) as pool:
                futures = [pool.submit(ll, ts_url, save_path = f'./{time.time()}.mp4') for ts_url in tasks]
                for fut in as_completed(futures):
                    print(fut.result())

            print("全部下载完成！")


        finally:
            # 统一在主线程收尾，避免 CancelledError
            try:
                browser.close()
            except Exception:
                pass

# https://vip.lz-cdn14.com/20221009/12939_4deebce7/1200k/hls/c2fa8f6a572000131.ts
if __name__ == '__main__':
    m3u8()
